package org.group6.aufgabe2;

import de.dailab.graphworld.ontology.Edge;
import de.dailab.graphworld.ontology.Node;
import de.dailab.graphworld.world.GraphWorldAgentBean;
import de.dailab.jiactng.agentcore.action.Action;
import de.dailab.jiactng.agentcore.ontology.IActionDescription;
import java.io.Serializable;
import java.util.ArrayList;
import java.util.Collection;
import java.util.Collections;
import java.util.List;
import org.group6.aufgabe2.memory.PathInfo;
import org.group6.utils.AgentUtils;

/**
 *
 * @author Kseniya
 */
public class BeanPheromone extends BeanMoving {

    private IActionDescription actionDropGoldPheromone;

    @Override
    public void doStart() throws Exception {
        super.doStart();
        actionDropGoldPheromone = thisAgent.searchAction(new Action(GraphWorldAgentBean.ACTION_DROP_GOLD_PHEROMONE));
    }

    @Override
    protected void dropGoldPheromones(Node target) {
        invoke(actionDropGoldPheromone, new Serializable[]{target}, this);
    }

    @Override
    protected Node selectMoveTarget(Collection<Node> explored) {
        // find node with max pheromone value on edge leading to it
        Node target = null;
        double maxPheromone = 0.0;
        Node curr = memory.read(new PathInfo(null, null)).path.peek();
        for (Node node : explored) {
            for (Edge edge : curr.getEdges()) {
                // round pheromone value to first digit after floating point 
                // to simplify the whole thing a little bit...
                double pheromoneRounded = AgentUtils.roundPheromone(edge.getPheromone().getGoldPheromone());
                if (edge.getTarget().getID() == node.getID()
                        && maxPheromone < pheromoneRounded) {
                    target = node;
                    maxPheromone = pheromoneRounded;
                }
            }
        }

        // now let's make the node with max pheromone (target) more probable to be selected

        // - 1 because target is already stored in explored
        int targetWeight = (int) (maxPheromone * AgentUtils.DELTA) - 1;

        List<Node> nodesWeighted = new ArrayList<>(explored.size() + targetWeight);
        nodesWeighted.addAll(explored);
        // make target more weighted
        if (targetWeight > 0) {
            nodesWeighted.addAll(Collections.nCopies(targetWeight, target));
        }
        Collections.shuffle(nodesWeighted);
        return super.selectMoveTarget(nodesWeighted);
    }
}
